#include "pch.h"
#include <mfidl.h>
#include "CCameraOcclusion.h"
#include "Utils.h"

# if SUPPORTTED_OCCLUSION_STATES

CCameraOcclusion::CCameraOcclusion()
	: m_nRefCount(1)
	, m_pCameraOcclusionStateMonitor(NULL)
{
}

CCameraOcclusion::~CCameraOcclusion()
{
	SafeRelease(&m_pCameraOcclusionStateMonitor);
}

STDMETHODIMP_(HRESULT) CCameraOcclusion::QueryInterface(REFIID iid, void** ppv)
{
	static const QITAB qit[] =
	{
		QITABENT(CCameraOcclusion, IMFCameraOcclusionStateReportCallback),
		{ 0 },
	};
	return QISearch(this, qit, iid, ppv);
}

STDMETHODIMP_(ULONG) CCameraOcclusion::AddRef()
{
	return InterlockedIncrement(&m_nRefCount);
}

STDMETHODIMP_(ULONG) CCameraOcclusion::Release()
{
	ULONG uCount = InterlockedDecrement(&m_nRefCount);
	if (uCount == 0)
	{
		delete this;
	}
	// For thread safety, return a temporary variable.
	return uCount;
}

HRESULT STDMETHODCALLTYPE CCameraOcclusion::OnOcclusionStateReport(IMFCameraOcclusionStateReport* occlusionStateReport)
{
	DWORD cameraOcclusionState = MFCameraOcclusionState_Open;
	HRESULT hr = occlusionStateReport->GetOcclusionState(&cameraOcclusionState);
	if (FAILED(hr))
	{
		AfxMessageBox(GetComExceptionMessage(hr));
	}
	else
	{
		switch (cameraOcclusionState)
		{
		case MFCameraOcclusionState_Open:
			AfxMessageBox(_T("MFCameraOcclusionState_Open"));
			break;
		case MFCameraOcclusionState_OccludedByLid:
			AfxMessageBox(_T("MFCameraOcclusionState_OccludedByLid"));
			break;
		case MFCameraOcclusionState_OccludedByCameraHardware:
			AfxMessageBox(_T("MFCameraOcclusionState_OccludedByCameraHardware"));
			break;
		}
	}

	return hr;
}

HRESULT CCameraOcclusion::CreateCameraOcclusionStateMonitor(LPCWSTR symbolicName)
{
	SafeRelease(&m_pCameraOcclusionStateMonitor);

	HRESULT hr = MFCreateCameraOcclusionStateMonitor(
		symbolicName,
		this,
		&m_pCameraOcclusionStateMonitor);

	if (FAILED(hr))
	{
		AfxMessageBox(GetComExceptionMessage(hr));
	}
	else
	{
		Release();
	}

	return hr;
}

#endif
